﻿using System;
using System.Net;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Documents;
using System.Windows.Ink;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Animation;
using System.Windows.Shapes;
using System.ComponentModel.Composition;
using System.Diagnostics;
using System.ComponentModel;
using System.Collections.Generic;
using System.Windows.Data;
using System.IO;
using System.Linq;
using Cinch;
using System.Configuration;
using System.Windows.Threading;


namespace Anata.Client
{
    /// <summary>
    /// </summary>
    public class CabangSelectViewModel : ViewModelBase
    {
        #region Data
        #region Data.Primitives
        private String filterKeyword = "";

        private bool isAllLoaded = false;
        private int pageLoaded = 0;
        private DispatcherTimer filterTimer;
        #endregion

        #region Data.Rules
        #endregion

        #region Data.VMs
        private DispatcherNotifiedObservableCollection<CabangThumbnailViewModel> cabangs;
        private ICollectionView cabangsCV;
        #endregion

        #region Data.Services
        private IViewAwareStatus viewAwareStatusService;
        private IMessageBoxService messageBoxService;
        private IUIVisualizerService uiVisualizerService;
        private IReferenceProvider referenceProvider;
        #endregion

        #endregion


        #region Constructor
        [ImportingConstructor]
        public CabangSelectViewModel(
            IMessageBoxService messageBoxService,
            IUIVisualizerService uiVisualizerService,
            IReferenceProvider referenceProvider)
        {
            #region Constructor.SetupServices
            this.messageBoxService = messageBoxService;
            this.uiVisualizerService = uiVisualizerService;
            //this.viewAwareStatusService = viewAwareStatusService;
            this.referenceProvider = referenceProvider;
            //this.viewAwareStatusService.ViewLoaded += ViewAwareStatusService_ViewLoaded;
            #endregion

            #region Constructor.SetupCommands
            CabangFilterKeyUpCommand = new SimpleCommand<Object, Object>(CanExecuteCabangFilterKeyUpCommand, ExecuteCabangFilterKeyUpCommand);
            CabangMouseLeftButtonUpCommand = new SimpleCommand<Object, Object>(CanExecuteCabangMouseLeftButtonUpCommand, ExecuteCabangMouseLeftButtonUpCommand);
            #endregion

            #region Constructor.SetupDataWrappers
            #endregion

            #region Constructor.SetupValidationRules
            #endregion

            #region Constructor.SetupVMs
            Cabangs = new DispatcherNotifiedObservableCollection<CabangThumbnailViewModel>();
            CabangsCV = CollectionViewSource.GetDefaultView(Cabangs);
            #endregion

            Mediator.Instance.Register(this);

            #region Constructor.Filter
            filterTimer = new DispatcherTimer();
            filterTimer.Interval = TimeSpan.FromMilliseconds(
                Int32.Parse(ConfigurationManager.AppSettings["FilterResponsiveness"].ToString()));
            filterTimer.Tick += new EventHandler(LazyFilterCallback);
            #endregion

            LoadCabangs();
        }
        #endregion

        #region Public Properties
        #region Public.Commands
        public SimpleCommand<Object, Object> CabangFilterKeyUpCommand { get; private set; }
        public SimpleCommand<Object, Object> CabangMouseLeftButtonUpCommand { get; private set; }
        #endregion

        #region Public.ViewMode
        #endregion

        #region Public.Data
        /// <summary>
        /// </summary>
        static PropertyChangedEventArgs filterKeywordChangeArgs =
            ObservableHelper.CreateArgs<CabangSelectViewModel>(x => x.FilterKeyword);
        public String FilterKeyword
        {
            get { return filterKeyword; }
            set
            {
                filterKeyword = value;
                NotifyPropertyChanged(filterKeywordChangeArgs);
                LazyFilter();
            }
        }
        #endregion

        #region Public.CachedCollection
        #endregion

        #region Public.DataVMs
        /// <summary>
        /// Loaded Konsumen
        /// </summary>
        static PropertyChangedEventArgs cabangsChangeArgs =
            ObservableHelper.CreateArgs<CabangSelectViewModel>(x => x.Cabangs);

        public DispatcherNotifiedObservableCollection<CabangThumbnailViewModel> Cabangs
        {
            get { return cabangs; }
            set
            {
                cabangs = value;
                NotifyPropertyChanged(cabangsChangeArgs);
            }
        }
        /// <summary>
        /// Loaded Konsumen
        /// </summary>
        static PropertyChangedEventArgs cabangsCVChangeArgs =
            ObservableHelper.CreateArgs<CabangSelectViewModel>(x => x.CabangsCV);

        public ICollectionView CabangsCV
        {
            get { return cabangsCV; }
            set
            {
                cabangsCV = value;
                NotifyPropertyChanged(cabangsCVChangeArgs);
            }
        }
        #endregion
        #endregion

        #region Command Handlers
        /// <summary>
        /// </summary>
        private bool CanExecuteCabangFilterKeyUpCommand(Object args)
        {
            return true;
        }
        /// <summary>
        /// </summary>
        private void ExecuteCabangFilterKeyUpCommand(Object args)
        {
            LazyFilter();
        }

        /// <summary>
        /// </summary>
        private bool CanExecuteCabangMouseLeftButtonUpCommand(Object args)
        {
            return true;
        }
        /// <summary>
        /// </summary>
        private void ExecuteCabangMouseLeftButtonUpCommand(Object args)
        {
            if (CabangsCV.CurrentPosition > -1)
            {
                CloseActivePopUpCommand.Execute(true);
            }
        }
        #endregion

        #region IViewStatusAwareInjectionAware Members
        #endregion

        #region Private Methods
        #region PrivateMethods.ViewLoaded
        private void ViewAwareStatusService_ViewLoaded()
        {
            LoadCabangs();
        }
        #endregion

        #region PrivateMethods.Filter
        private void LazyFilter()
        {
            filterTimer.Stop();
            filterTimer.Start();
            Console.WriteLine("typing");
        }
        private void LazyFilterCallback(object sender, EventArgs e)
        {
            Console.WriteLine("stopped typing, filtering with keyword: " + filterKeyword);
            filterTimer.Stop();
            if (filterKeyword != "")
            {
                CabangsCV.Filter = new Predicate<object>(LazyFilterPredicate);
            }
            else
            {
                CabangsCV.Filter = null;
            }
        }
        private bool LazyFilterPredicate(object row)
        {
            KaryawanThumbnailViewModel ktvm = row as KaryawanThumbnailViewModel;
            return (ktvm.Nama.ToLower().Contains(filterKeyword.ToLower()));
        }
        #endregion

        #region PrivateMethods.Loader
        /// <summary>
        /// loader
        /// </summary>
        private void LoadCabangs()
        {
            referenceProvider.LazyFetchCabangs(pageLoaded, PostLoadCabangs);
        }

        /// <summary>
        /// post loader
        /// </summary>
        private void PostLoadCabangs(List<CabangThumbnailViewModel> ctvms)
        {
            //rekursif sampai semua diload
            int pageSize = Int32.Parse(ConfigurationManager.AppSettings["LazyLoadPageSize"].ToString());
            foreach (var ctvm in ctvms)
            {
                Cabangs.Add(ctvm);
            }

            if (ctvms.Count != pageSize)
            {
                //basis
                //sudah habis, done loading
                isAllLoaded = true;
            }
            else
            {
                //rekurens
                ++pageLoaded;
                LoadCabangs();
            }
        }
        #endregion
        #endregion
    }

}
